﻿import QtQuick 2.3
import QtQuick.Controls 1.2
import QmlObjectTest 1.0
import QtQuick.Dialogs 1.2
import QtQuick.Window 2.2
import QtQuick.Controls.Styles 1.4
import QtQuick.Controls.Private 1.0
import QtMultimedia 5.5

import "qml/"

//import MyCommon 1.0

ApplicationWindow {
    id: window
    visible: true
    width: Screen.width
    height: Screen.height
    title: qsTr("萌梦泡泡龙")


    property real value: 0
    property int result: -1
    property bool bStartGame: true
    property real step: 50

    property real score: 0

    property real speed: 30

    property bool isFired: false

    property int touchYaoGan: 0     //0=没有，1=触控点1占用，2=触控点2占用
    property int touchSpeed: 0    //0=没有，1=触控点1占用，2=触控点2占用

    property real maxScore: 0

    property bool canPress: true

    property real moveAngle: 0  //移动方向

    property real ballRadius: 50

    property var fireBall: undefined    //当前发射球

    property var tempArray: new Array
    property int tempArrayCaiji: 0

    property int tempNewI: 0
    property int tempNewJ: 0
    property int tempNewType: 0

    property int ballScore: 100

    property bool clear: false


    Component.onCompleted: {
//        maxScore = common.getScore()

        fireItem.create()
    }

//    onMaxScoreChanged: {
//        common.saveScore(maxScore)
//    }

    function addZero(value){
        if(value < 10){
            return "0" + value
        }
        return value
    }

    function getSeed(){

        var date = new Date
        var y = date.getFullYear()
        var M = addZero(date.getMonth())
        var d = addZero(date.getDate())
        var h = addZero(date.getHours())
        var m = addZero(date.getMinutes())
        var s = addZero(date.getSeconds())

        var time = String(y) + String(M) + String(d) + String(h) + String(m) + String(s)

        return Number(time)
    }

    function calcAngle(pressX, pressY){
        var centerX = fireBall.x + fireBall.width/2
        var centerY = fireBall.y + fireBall.height/2

        var radian = Math.atan2(pressY - centerY, pressX - centerX )

        var angle = 180 / Math.PI * radian

        //防止向下
        if(angle>0){
            angle = -angle
        }

        //限制角度
        if(angle<-160){
            angle = -160
        }
        if(angle>-30){
            angle = -30
        }

        line.angle = angle
        moveAngle = angle

        line.visible = true
    }

    function checkScreen(x, y){
        var w = Screen.width
        var h = Screen.height
        var radian = Math.PI/180 * moveAngle

        var point = Qt.point(x,y)

        if(x<=2/* && moveAngle<-90*/){
            moveAngle = -(180+moveAngle)
            point.x = 2
            point.y = (fireBall.x-2)*Math.tan(radian) + fireBall.y
        }
        else if(x+ballRadius*2+2>=w /*&& moveAngle>-90*/){
            moveAngle = 180-moveAngle
            point.x = w-ballRadius*2-2
            point.y = (w-fireBall.x-ballRadius*2-2)*Math.tan(radian) + fireBall.y
        }

        return point
    }

    function checkBallAndBall(pointA, pointB){
        //检测球碰到
        var ax = pointA.x
        var ay = pointA.y

        var bx = pointB.x
        var by = pointB.y

        var dt = Math.sqrt(Math.abs(ax-bx)*Math.abs(ax-bx) + Math.abs(ay-by)*Math.abs(ay-by))

        if(dt <= ballRadius*2){
            return true
        }

        return false
    }

    function calcScorePlay(newI, newJ, tempType){
        //形成 3 个或以上的同色泡泡相连，则这些泡泡将爆掉
//        console.log("calcScorePlay ", newI, newJ, tempType)

        //构建数据集
        tempArray = new Array
        tempArray.length = 0
        for(var i=0 in level.arrays){
            var temp = level.arrays[i]
            var t = new Array
            for(var j=0; j<temp.length; j++){
                t.push(0)
            }
            tempArray.push(t)
        }
        tempArray[newI][newJ] = 1
        tempArrayCaiji = 1

        //计算 采集
        checkSameTypeSize(newI, newJ, tempType)

//        console.log("tempArrayCaiji=", tempArrayCaiji)
        //消 追加动画
        if(tempArrayCaiji>=3){
            for(var a=0 in tempArray){
                var t = tempArray[a]
                for(var b=0 in t){
                    if(t[b] == 1){
                        //消灭泡泡
                        level.arrays[a][b] = 0
                        level.balls[a][b].distroyBall()

                        //计分
//                        score += ballScore
                        textItem.create(a,b)
                        playSound.play()
                    }
                }
            }
        }

        //检测是否清除所有泡泡
        clear = true
        for(var i=0 in level.arrays){
            var line = level.arrays[i]
            for(var j=0 in line){
                if(line[j] != 0){
                    clear = false
                    break
                }
            }
            if(!clear){
                break
            }
        }
        if(clear){
            nextLevelScreen.scale = 1
            canPress = false
        }

    }

    //发射球粘连后
    function handleZhanLianHou(){
        level.addOne(tempNewI, tempNewJ, tempNewType)

        if(tempNewI >= 13){
            //死亡
            bStartGame = false
            options.scale = 1
            options.focus = true

            fireItem.create()
            canPress = true
        }
        else{
            calcScorePlay(tempNewI, tempNewJ, tempNewType)

            fireItem.create()
            canPress = true
        }
//        console.log("==========================", canPress)
    }

    function checkSameTypeSize(newI, newJ, tempType){
//        console.log("checkSameTypeSize ", newI, newJ, tempType)
        var hasSize = 0
        var flag = newI%2
        var len = flag==0?9:10
        var otherLen = flag==1?9:10

        var tempPoint = new Array

        //左侧泡泡
        if(newJ-1>=0){
            if(level.arrays[newI][newJ-1] == tempType){
                tempPoint.push(Qt.point(newI, newJ-1))
            }
        }

        //右侧泡泡
        if(newJ+1<=len-1){
            if(level.arrays[newI][newJ+1] == tempType){
                tempPoint.push(Qt.point(newI, newJ+1))
            }
        }
        //上侧
        if(newI-1>=0){

            if(flag==0){
                //上层是偶数行
                if(newJ>=0){
                    //上左侧泡泡
                    //上左侧 存在
                    if(level.arrays[newI-1][newJ] == tempType){
                        tempPoint.push(Qt.point(newI-1, newJ))
                    }
                }
                 //上右侧泡泡
                if(newJ+1<=otherLen-1){
                    //存在
                    if(level.arrays[newI-1][newJ+1] == tempType){
                        tempPoint.push(Qt.point(newI-1, newJ+1))
                    }
                }
            }
            else{
                //上层是奇数行
                if(newJ-1>=0){
                    //上左侧泡泡
                    //上左侧 存在
                    if(level.arrays[newI-1][newJ-1] == tempType){
                        tempPoint.push(Qt.point(newI-1, newJ-1))
                    }
                }
                 //上右侧泡泡
                if(newJ<=otherLen-1){
                    //存在
                    if(level.arrays[newI-1][newJ] == tempType){
                        tempPoint.push(Qt.point(newI-1, newJ))
                    }
                }
            }

        }

        //下侧
        if(newI+1<level.arrays.length){
            if(flag==0){
                //下层是偶数行
                if(newJ>=0){
                    //下左侧泡泡
                    //下左侧 存在
                    if(level.arrays[newI+1][newJ] == tempType){
                        tempPoint.push(Qt.point(newI+1, newJ))
                    }
//                    console.log("下左侧泡泡=", newI, newJ, level.arrays[newI+1][newJ])
                }
                 //下右侧泡泡
                if(newJ+1<=otherLen-1){
                    //存在
                    if(level.arrays[newI+1][newJ+1] == tempType){
                        tempPoint.push(Qt.point(newI+1, newJ+1))
                    }
//                    console.log("下右侧泡泡=", newI, newJ, level.arrays[newI+1][newJ+1])
                }
            }
            else{
                //下层是奇数行
                if(newJ-1>=0){
                    //下左侧泡泡
                    //下左侧 存在
                    if(level.arrays[newI+1][newJ-1] == tempType){
                        tempPoint.push(Qt.point(newI+1, newJ-1))
                    }
//                    console.log("下层是奇数行 下左侧=", newI, newJ, level.arrays[newI+1][newJ-1])
                }
                 //下右侧泡泡
                if(newJ<=otherLen-1){
                    //存在
                    if(level.arrays[newI+1][newJ] == tempType){
                        tempPoint.push(Qt.point(newI+1, newJ))
                    }
//                    console.log("下层是奇数行 下右侧泡泡=", newI, newJ, level.arrays[newI+1][newJ])
                }
            }
        }

        var tempArrayFunc = new Array

        for(var p=0 in tempPoint){
            var pp = tempPoint[p]
            if(tempArray[pp.x][pp.y]==1){
                //已经采集过这个点
//                console.log("已经采集过这个点", pp)
            }
            else{
                tempArray[pp.x][pp.y] = 1
                tempArrayCaiji++
                tempArrayFunc.push(Qt.point(pp.x, pp.y))
            }
        }

        //test
        for(var p=0 in tempArrayFunc){
            var pp = tempArrayFunc[p]
//            console.log("============pp", pp)
        }
        //递归采集
        for(var p=0 in tempArrayFunc){
            var pp = tempArrayFunc[p]
            checkSameTypeSize(pp.x, pp.y, tempType)
        }

    }

//    MyCommon{
//        id: common
//    }

    Rectangle{
        id: rectBgMain
        anchors.fill: parent
        color: Qt.rgba(219/255, 199/255, 129/255, 1)

        focus: true

        Keys.onBackPressed: {
            if(!bStartGame) return
            options.focus = true
            options.scale = 1
            bStartGame = false
        }
    }


    //Text
    Label{
        id: textLevelLabel
        text: "关卡: " + level.currentLevel
        font.pointSize: 20
        font.family: "微软雅黑"
        x: textScoreLabel.x
        y: textScoreLabel.y - height - 10
        z: 11
        color: "white"
        font.bold: true
    }
    Label{
        id: textScoreLabel
        text: "分数: " + score
        font.pointSize: 20
        font.family: "微软雅黑"
        x: 100
        y: parent.height-100 - 80
        z: 11
        color: "white"
        font.bold: true
    }

    //死亡线
    Rectangle{
        id: rectDeath
        width: parent.width
        height: 3
        color: "red"
        y: 1300
    }

    //level
    Level{
        id: level
    }

    //发射球
//    FireBall{
//        id: fireBall
//    }

    //发射球
    Item{
        id: fireItem
        anchors.fill: parent

        property var fireBalls: new Array

        function create(){
            var obj = Qt.createComponent("qml/FireBall.qml").createObject(fireItem)
            obj.ready()

            fireBall = obj

            fireBalls.push(obj)

            line.x = fireBall.x + fireBall.width/2
            line.y = fireBall.y + fireBall.height/2
        }
    }
    //分数tip
    Item{
        id: textItem
        width: ballRadius*2*10 + 5*(10-1)
        anchors.horizontalCenter: parent.horizontalCenter
        y: 10

        function create(pointX, pointY){
//            console.log("main.qml textItem",pointX, pointY )
            var obj = Qt.createComponent("qml/TextScore.qml").createObject(textItem)

            obj.y = pointX*ballRadius*2-7*pointX + (ballRadius-obj.height/2)
            if(pointX%2==0){
                //奇数
                obj.x = ballRadius + pointY*(ballRadius*2+5) + (ballRadius - obj.width/2)
            }
            else{
                obj.x = pointY*(ballRadius*2+5) + (ballRadius - obj.width/2)
            }

//            console.log("---------", obj.x, obj.y)

            obj.move()
        }
    }

    //虚线
    Line{
        id: line
        visible: false        
    }


    //鼠标感应区
    MouseArea{
        id: mouse
        anchors.fill: parent
        enabled: canPress && bStartGame
        onPressed: {
            calcAngle(mouse.x, mouse.y)
        }
        onPositionChanged: {
            calcAngle(mouse.x, mouse.y)
        }
        onReleased: {
            line.visible = false
            if(fireBall)
                fireBall.fire()
        }
    }

    //options
    MouseArea{
        id: optionsMouse
        anchors.fill: parent
        enabled: options.scale==1?true:false
        z: 100

        Options{
            id: options
            anchors.centerIn: parent
        }
    }

    LevelScreen{
        id: levelScreen
        anchors.centerIn: parent
    }

    NextLevelScreen{
        id: nextLevelScreen
        anchors.centerIn: parent
    }

    SoundEffect {
        id: playSound
        source: "qrc:/music/music/eat1.wav"
    }


    Timer{
        id: timerGame
        interval: speed
        repeat: true
        running: bStartGame
        onTriggered: {
            if(fireBall && fireBall.canMove){
                //发射小球
                canPress = false
                var radian = Math.PI/180 * moveAngle
                var x = Math.cos(radian) * step
                var y = Math.sin(radian) * step

                var point = checkScreen(fireBall.x + x, fireBall.y + y)

//                fireBall.x = point.x
//                fireBall.y = point.y

                var tempType = fireBall.type

                //上边界检测
                if(point.y <= 2){

                    //将球归位到正点上
                    var leftX
                    var newI, newJ
                    newI = 0
                    newJ = 0
                    if(point.x+ballRadius<ballRadius){
                        newJ = 0
                    }
                    else if(point.x+ballRadius>ballRadius + 8*(ballRadius*2+5)){
                        newJ = 8
                    }
                    else{
                        for(var jj=0; jj<9; jj++){
                           leftX = ballRadius + jj*(ballRadius*2+5)

                           if(point.x+ballRadius >= leftX && point.x+ballRadius <= leftX + ballRadius*2+5){
                               newJ = jj
                               break
                           }
                        }
                    }


                    tempNewI = newI
                    tempNewJ = newJ
                    tempNewType = tempType

                    var pointTemp = Qt.point(0,0)

                    if(newI%2==0){
                        //奇数
                        pointTemp.x = ballRadius + newJ*(ballRadius*2+5)
                    }
                    else{
                        //偶数
                        pointTemp.x = newJ*(ballRadius*2+5)
                    }
                    pointTemp.x += (Screen.width-955)/2
                    pointTemp.y = newI*ballRadius*2-7*newI + 10

                    fireBall.moveToPoint(pointTemp)

                }
                else{
                    //行
//                    console.log("--", level.balls.length)
                    var rr = false
                    for(var i=level.balls.length-1;i>=0; i--){
                        var ib = level.balls[i]
                        var r = false
                        //列
//                        console.log("-列-", ib.length)
                        for(var j=0 in ib){
                            var b = ib[j]
                            if(b.type==0) continue

                            var pointA = Qt.point(b.x+ballRadius, b.y+ballRadius)
                            var pointB = Qt.point(point.x+ballRadius, point.y+ballRadius)
                            var result = checkBallAndBall(pointA, pointB)
                            if(result){                                

                                r = true

                                //计算角度
                                var radian = Math.atan2(pointB.y - pointA.y, pointB.x - pointA.x )

                                var angle = 180 / Math.PI * radian

                                //将球归位到正点上
                                var newI, newJ

                                if(angle>=30 && angle<=90){
                                    //右下角
                                    newI = Number(i)+1
                                    if(i%2==0){
                                        //奇数行
                                        newJ = Number(j)+1
                                    }
                                    else{
                                        newJ = Number(j)
                                    }
                                }
                                else if(angle>90 && angle<=150){
                                    //左下角
                                    newI = Number(i)+1
                                    if(i%2==0){
                                        //奇数行
                                        newJ = Number(j)
                                    }
                                    else{
                                        newJ = Number(j)-1
                                    }
                                }
                                else if(angle<30 && angle>=-30){
                                    //右
                                    newI = Number(i)
                                    newJ = Number(j)+1
                                }
                                else if(angle<-30 && angle >= -90){
                                    //右上角
                                    newI = Number(i)-1
                                    if(i%2==0){
                                        //奇数行
                                        newJ = Number(j)+1
                                    }
                                    else{
                                        newJ = Number(j)
                                    }
                                }
                                else if(angle<-90 && angle >= -150){
                                    //左上角
                                    newI = Number(i)-1
                                    if(i%2==0){
                                        //奇数行
                                        newJ = Number(j)
                                    }
                                    else{
                                        newJ = Number(j)-1
                                    }
                                }
                                else{
                                    //左
                                    newI = Number(i)
                                    newJ = Number(j)-1
                                }

                                //越界处理
                                if(newI<0) newI = 0
                                if(newI>=level.arrays.length) newI = level.arrays.length-1

                                if(newJ<0) newJ = 0
                                if(newI%2==0){
                                    //奇数行
                                    newJ = Math.min(newJ, 8)
                                    newJ = Math.max(newJ, 0)
                                }
                                else{
                                    newJ = Math.min(newJ, 9)
                                    newJ = Math.max(newJ, 0)
                                }

                                tempNewI = newI
                                tempNewJ = newJ
                                tempNewType = tempType

                                var pointTemp = Qt.point(0,0)

                                if(newI%2==0){
                                    //奇数
                                    pointTemp.x = ballRadius + newJ*(ballRadius*2+5)
                                }
                                else{
                                    //偶数
                                    pointTemp.x = newJ*(ballRadius*2+5)
                                }
                                pointTemp.x += (Screen.width-955)/2
                                pointTemp.y = newI*ballRadius*2-7*newI+10

                                fireBall.moveToPoint(pointTemp)

                                break
                            }
                        }
                        if(r){
                            rr = true
                            break
                        }
                    }
                    if(!rr){
                        //没碰撞其他球
                        fireBall.x = point.x
                        fireBall.y = point.y
                    }
                }
            }
        }
    }

}

